在建立工作流程的流水線時,流水線上的每個工作都要作嗎?我想這不是一定的。像是部署的程序,就會希望在產品開發到一的段落,在特定 Git 分支或上 Git Tag 的時候才執行;另外,像測試工作,為了節省流水線的進行效率,會希望前端程式有更動時,才執行前端的測試,後端的程式更動,才執行後端的測試;甚至有些工作,希望在有需求的時候才透過「手動」來決定要不要執行。這些,在 GitLab CI 上,要怎麼來完成呢?接下來會分兩篇左右的內容來說明 GitLab CI 的各種場景的執行條件設定。
.gitlab-ci.yml
中透過 when
系列語法來讓決定什麼時候執行在 .gitlab-ci.yml
中,只需要在 job 的描述中加上 when
以及部分參數即可以達到在特定時候才執行該工作。在目前 GitLab CI 裡總共提供了以下的語法:
on_success
:這個工作只在前一個關卡(stage) 的工作成功執行時執行。(這是 GitLab CI 的預設值),另外當前一份工作有設定 allow_failure: true
屬性時,這個工作會視為前一關卡成功,而執行。on_failure
:這個工作只在前一個關卡 (stage) 的工作執行失敗時才執行。這個屬性常見的使用場合像是,上一份工作失敗後,幫忙做環境的重置或執行環境整理。always
:無論前一關卡的工作 (stage) 成功與失敗,皆會執行。manual
:手動執行。必須注意,當設定為手動執行時,其預設會將該工作 allow_failure
屬性設定為 true
,這會導致下一關卡的工作不等此工作是否執行完畢,便開始執行。delayed
:延遲一段時間後開始執行,搭配 start_in
語法,其時間設定的語法概略如下:
delay:running:
stage: deploy
script: echo 'delay 30 minutes'
when: delayed
start_in: 30 minutes
時間單位預設為「秒」,可使用的範例如下:
'5'
5 seconds
30 minutes
1 day
1 week
never
:搭配 rules
及 workflow:rules
參數使用。在上方關於手動執行的描述中有提到「當設定為手動執行時,其預設會將該工作 allow_failure
屬性設定為 true
」這部分必須要特別注意,以底下的例子:
default:
image: ubuntu:20.04
build:
stage: build
script:
- echo "BUILD_VERSION=hello" >> variable.env
- echo "BUILD_NAME=GitLab" >> variable.env
when: manual
deploy:
stage: deploy
script:
- echo 'do deploy process'
在上面的這例子執行結果中可以看到,在 build 的工作還沒執行,後續 deploy 關卡的工作便開始執行。這就是因為上述的,因為其「工作 allow_failure
屬性被預設為 true
」。
因此,如果手動關卡後續的工作,必須在此工作正確執行完成後才能執行,則必須為工作設定上 allow_failure: false
參數。
default:
image: ubuntu:20.04
build:
stage: build
script:
- echo "BUILD_VERSION=hello" >> variable.env
- echo "BUILD_NAME=GitLab" >> variable.env
when: manual
allow_failure: false
deploy:
stage: deploy
script:
- echo 'do deploy process'
如上範例的調整,其後續的工作即被設定在等待 Build 關卡正確執行的狀態。
上述的語法,也可以在 CI Lint 的介面中看到,當未設定 allow_failure: false
時,顯示使用了 when: manual
語法,並且設定了 allowed to fail
。
當設定了 allowed to fail
則測試結果則會改變為,原本的 allowed to fail
描述消失了。
在使用 when
語法的時候,必須要特別注意設定「手動」時 allow_failure
的屬性變化,另外,也可以透過 CI Lint 這個工具來協助查錯。
關於流水線工作的執行條件,還有 only
、except
以及 rules
可以控制,因此下一篇將繼續討論更細節的流水線工作流程條件的設定。我是墨嗓(陳佑竹),期待這系列的文章能夠讓人有些幫助。